package com.visionet.waveletData.web.web.plan;

import com.alibaba.fastjson.JSONObject;
import com.google.common.collect.Maps;
import com.visionet.waveletData.web.common.security.password.RequestSignUtil;
import com.visionet.waveletData.web.common.utilities.props.PropsKeys;
import com.visionet.waveletData.web.common.utilities.props.PropsUtil;
import com.visionet.waveletData.web.common.utils.DateUtils;
import com.visionet.waveletData.web.common.utils.FileMd5Util;
import com.visionet.waveletData.web.common.utils.OssBackup;
import com.visionet.waveletData.web.entity.group.Group;
import com.visionet.waveletData.web.entity.plan.PlanFile;
import com.visionet.waveletData.web.entity.plan.PlayGroup;
import com.visionet.waveletData.web.entity.plan.PlayPlan;
import com.visionet.waveletData.web.service.account.ShiroDbRealm;
import com.visionet.waveletData.web.service.account.ShiroDbRealm.ShiroUser;
import com.visionet.waveletData.web.service.group.GroupService;
import com.visionet.waveletData.web.service.plan.PlanFileService;
import com.visionet.waveletData.web.service.plan.PlanGroupService;
import com.visionet.waveletData.web.service.plan.PlayPlanService;
import com.visionet.waveletData.web.vo.GroupVo;
import com.visionet.waveletData.web.vo.SysPlanDataVo;
import com.visionet.waveletData.web.vo.plan.PlanFileVo;
import com.visionet.waveletData.web.vo.plan.PlanGroupVo;
import com.visionet.waveletData.web.vo.plan.PlayPlanVo;
import com.visionet.waveletData.web.web.BaseController;
import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.jivesoftware.smack.util.MD5;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.domain.Page;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.multipart.commons.CommonsMultipartFile;
import org.springside.modules.mapper.BeanMapper;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.net.URL;
import java.net.URLConnection;
import java.net.URLDecoder;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Controller
@RequestMapping(value="/playPlanContoller")
public class PlayPlanContoller extends BaseController{

	public final static Logger logger = LoggerFactory.getLogger(PlayPlanContoller.class);

	@Resource
	private PlayPlanService playPlanService;

	@Resource
	private PlanFileService planFileService;

	@Resource
	private GroupService groupService;

	@Resource
	private PlanGroupService planGroupService;

	private OssBackup ossBackup = new OssBackup();
	/**
	 * 查询播放计划
	 * @param playPlanVo
	 * @return
	 */
	@RequestMapping(value = "/playPlanList", method = RequestMethod.POST)
	public ResponseEntity<?> playPlanList(@RequestBody PlayPlanVo playPlanVo) {
		//PlayPlan playPlan = BeanMapper.map(playPlanVo, PlayPlan.class);
		//Page<PlayPlan> page = playPlanService.findPlayPlanByConditionForList(playPlan, playPlanVo.getPageInfo());

		ShiroDbRealm.ShiroUser suser = (ShiroDbRealm.ShiroUser) SecurityUtils.getSubject().getPrincipal();
		if(suser == null){
			throw new RuntimeException("未登录");
		}
		playPlanVo.setCompanyId(suser.getCompanyId());
		Page<PlayPlanVo>  page = playPlanService.findPlayPlanPage(playPlanVo, playPlanVo.getPageInfo());
		/*List<PlayPlan> list = page.getContent();
		List<PlayPlanVo> volist = BeanMapper.mapList(list, PlayPlanVo.class);*/

		return new ResponseEntity<Page<PlayPlanVo>>(page,HttpStatus.OK);
	}
	/**
	 * 修改播放计划
	 * @param playPlanVo
	 * @return
	 */
	@RequestMapping(value = "/updatePlayPlan")
	public ResponseEntity<?> updatePlayPlan(@RequestBody PlayPlanVo playPlanVo) {
		playPlanService.updatePlayPlan(playPlanVo);
		return new ResponseEntity<Map<String,String>>(GetSuccMap() ,HttpStatus.OK);
	}
	/**
	 * 删除播放计划
	 * @param id
	 * @return
	 */
	@RequestMapping(value = "/deletePlayPlan/{id}")
	public ResponseEntity<?> deletePlayPlan(@PathVariable Long id) {
		playPlanService.deletePlayPlan(id);

		return new ResponseEntity<Map<String,String>>(GetSuccMap() ,HttpStatus.OK);
	}
	/**
	 * 新增和修改播放计划
	 * @param
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/addPlayPlan", method = RequestMethod.POST)
	public ResponseEntity<?> addPlayPlan(@RequestBody PlayPlanVo playPlanVo) throws Exception {
		PlayPlan playPlan = null;
		String companyId = getCurrentUserCompanyId();
		if(null ==playPlanVo.getId()){
			List<PlayPlan> lists = playPlanService.findByPlanName(playPlanVo.getPlanName(),companyId);
			if(null != lists && lists.size()>0){
				Map<String, Object> result = Maps.newHashMap();
		        result.put("fail", "播放计划名称已存在");
		        return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
			}
			playPlan = new PlayPlan();
			playPlan.setCompanyId(companyId);
			playPlan.setVideoNum(Integer.valueOf("0"));
			playPlan.setGroupNum(Integer.valueOf("0"));
			playPlan.setIs_deleted("0");
			playPlan.setCreateBy("admin");
			playPlan.setCreateDate(new Date());
			playPlan.setUpdateBy("admin");
			playPlan.setUpdateDate(new Date());
		}else{
			List<PlayPlan> lists = playPlanService.findByPlanNameAndPlanId(playPlanVo.getPlanName(),playPlanVo.getId() );
			if(null != lists && lists.size()>0){
				Map<String, Object> result = Maps.newHashMap();
		        result.put("fail", "播放计划名称已存在");
		        return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
			}
			playPlan = playPlanService.findPlayPlanById(playPlanVo.getId());
			playPlan.setUpdateDate(new Date());
		}
		playPlan.setPlanName(playPlanVo.getPlanName());
		Long planId = playPlanService.savePlanPlan(playPlan);
		playPlanService.curdPlanData(planId);
	    Map<String, Object> result = Maps.newHashMap();
	    result.put("planId", planId);
	    result.put("success", "保存成功");
	    return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
	}
	public static String getCurrentUserCompanyId() {
		ShiroUser user = (ShiroUser) SecurityUtils.getSubject().getPrincipal();
		if (user == null) {
			throw new RuntimeException("未登陆！");
        }
		if (isAgency() && user.companyId != null) {
			return user.companyId;
		}
		return user.companyId;
	}
	/**
	 * 查询播放文件和分组
	 * @param planFileVo
	 * @return
	 */
	@RequestMapping(value = "/fileAndGroupList",method=RequestMethod.POST)
	public ResponseEntity<Map<String, Object>> fileAndGroupList(@RequestBody PlanFileVo planFileVo) {

		Map<String, Object> result = Maps.newHashMap();
		List<PlanFileVo> planFiles = planFileService.findPlanFileByPlanId(planFileVo.getPlanId());
		result.put("planFiles", planFiles);
		List<PlanGroupVo> plangroups = planGroupService.findPlanGroupByPlanId(planFileVo.getPlanId());
		result.put("plangroups", plangroups);
		String planName = playPlanService.findPlayPlanById(Long.valueOf(planFileVo.getPlanId())).getPlanName();
		result.put("planName", planName);
		return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
	}
	/**
	 * 新增播放文件
	 * @param planFile
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/addFile", method = RequestMethod.POST)
	public ResponseEntity<?> addFile(@RequestBody PlanFile planFile) throws Exception {
		PlanFile p = new PlanFile();
		if(StringUtils.isEmpty(planFile.getFilePath())){
			Map<String, Object> result = Maps.newHashMap();
	        result.put("nofile", "请选择文件");
	        return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
		}
		List<PlanFile> lists = planFileService.findByFileNameAndPlanId(planFile.getFileName(),planFile.getPlanId());
		if(null !=lists && lists.size()>0){
			Map<String, Object> result = Maps.newHashMap();
	        result.put("fail", "视频名称已存在");
	        return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
		}
		String path = PropsUtil.getProperty(PropsKeys.UPLOAD_FILE_PATH);
		URL url = new URL(path+planFile.getFilePath());
		String fileType = planFile.getFilePath().substring(planFile.getFilePath().lastIndexOf(".")+1);
		String filePath =planFile.getFilePath().substring(0,planFile.getFilePath().lastIndexOf(".")); 
	    URLConnection uc = url.openConnection();
		p.setFileName(planFile.getFileName());
		p.setFileType(fileType);
		p.setFileSize(uc.getContentLength());
		p.setFilePath(filePath);
		p.setPlanId(planFile.getPlanId());
		p.setFileMd5(planFile.getFileMd5());
		p.setStartTime(DateUtils.getStartTimeOfDay(planFile.getStartTime()));
		p.setEndTime(DateUtils.getEndTimeOfDay(planFile.getEndTime()));
		p.setIs_deleted("0");
		p.setCreateBy("admin");
		p.setCreateDate(new Date());
		p.setUpdateBy("admin");
		p.setUpdateDate(new Date());
		planFileService.savePlanFile(p);
		//修改播放计划修改时间
		PlayPlan playPlan = playPlanService.findPlayPlanById(Long.valueOf(planFile.getPlanId()));
		playPlan.setUpdateDate(new Date());
		playPlanService.savePlanPlan(playPlan);
		if(playPlan != null){
			playPlanService.curdPlanData(playPlan.getId());
		}
	    Map<String, Object> result = Maps.newHashMap();
	    result.put("success", "保存成功");
	    return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
	}
	/**
	 * 删除播放文件
	 * @param id
	 * @return
	 */
	@RequestMapping(value = "/deletePlanFile/{id}")
	public ResponseEntity<?> deletePlanFile(@PathVariable Long id) {
		planFileService.deletePlanFile(id);
		return new ResponseEntity<Map<String,String>>(GetSuccMap() ,HttpStatus.OK);
	}

	/**
	 * 查询分组
	 * @param groupVo
	 * @return
	 */
	@RequestMapping(value = "/groupList", method = RequestMethod.POST)
	public ResponseEntity<?> groupList(@RequestBody GroupVo groupVo) {
		Group group = BeanMapper.map(groupVo, Group.class);
		ShiroDbRealm.ShiroUser suser = (ShiroDbRealm.ShiroUser) SecurityUtils.getSubject().getPrincipal();
		if(suser == null){
			throw new RuntimeException("未登录");
		}
		groupVo.setCompanyId(suser.getCompanyId());
		Page<GroupVo> page = groupService.findGroupByConditionForList(groupVo, groupVo.getPageInfo());
		List<GroupVo> volist = BeanMapper.mapList(page.getContent(), GroupVo.class);

		return new ResponseEntity<Page<GroupVo>>(GetPageByList(page,volist, GroupVo.class),HttpStatus.OK);
	}
	/**
	 * 新增播放分组
	 * @param playGroup
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/addGroup", method = RequestMethod.POST)
	public ResponseEntity<?> addGroup(@RequestBody PlayGroup playGroup) throws Exception {
		List<PlayGroup> planGroup = planGroupService.findPlanGroupByPlanIdAndGroupId(playGroup.getPlanId(), playGroup.getGroupId());
		if(planGroup!=null && planGroup.size()>0){
			 Map<String, Object> result = Maps.newHashMap();
			    result.put("fail", "保存失败，该播放分组已存在");
			    return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
		}
		PlayGroup p = new PlayGroup();
		p.setPlanId(playGroup.getPlanId());
		p.setGroupId(playGroup.getGroupId());
		p.setCreateBy("admin");
		p.setCreateDate(new Date());
		p.setUpdateBy("admin");
		p.setUpdateDate(new Date());
		p.setIs_deleted("0"); 
		planGroupService.savePlanGroup(p);
		groupService.updateGroup(playGroup.getPlanId(), Long.valueOf(playGroup.getGroupId()));
		//修改播放计划修改时间
		PlayPlan playPlan = playPlanService.findPlayPlanById(Long.valueOf(playGroup.getPlanId()));
		playPlan.setUpdateDate(new Date());
		playPlanService.savePlanPlan(playPlan);
		if(playPlan != null){
			playPlanService.curdPlanData(playPlan.getId());
		}
	    Map<String, Object> result = Maps.newHashMap();
	    result.put("success", "保存成功");
	    return new ResponseEntity<Map<String, Object>>(result, HttpStatus.OK);
	}
	/**
	 * 删除播放分组
	 * @param id
	 * @return
	 */
	@RequestMapping(value = "/deletePlanGroup/{id}")
	public ResponseEntity<?> deletePlanGroup(@PathVariable Long id) {
		planGroupService.deletePlanGroup(id);
		return new ResponseEntity<Map<String,String>>(GetSuccMap() ,HttpStatus.OK);
	}
	/**
	 * 文件上传
	 * @param
	 * @return
	 * @throws Exception
	 */
	@RequestMapping("/upload")
	@ResponseBody
	public ResponseEntity<?> upload(HttpServletRequest request) throws Exception{
		HashMap<String,String> map = new HashMap<>();
		try {
			MultipartHttpServletRequest multipartRequest = (MultipartHttpServletRequest) request;
			Map<String, MultipartFile> fileMap = multipartRequest.getFileMap();
			for (Map.Entry<String, MultipartFile> entity : fileMap.entrySet()) {
				MultipartFile file = entity.getValue();
				String fileName = URLDecoder.decode(file.getOriginalFilename(), "UTF-8");
				String prefix=fileName.substring(fileName.lastIndexOf(".")+1);
				String md5FileName = MD5.hex(fileName);
				CommonsMultipartFile cf = (CommonsMultipartFile) file;
				InputStream inputStream = cf.getInputStream();
				/**
				 * 拷贝inputstream，分别用于生成文件MD5，和上传至阿里云
				 */
				byte [] byteArr=file.getBytes();
				InputStream fileMd5InputStream = new ByteArrayInputStream(byteArr);

				String md5 = FileMd5Util.fileMD5ByStream(fileMd5InputStream);
				logger.info("文件MD5生成成功======================================================");

				ossBackup.putObject(inputStream, "pb", md5FileName+"."+prefix, file.getSize());
				logger.info("文件上传成功======================================================");

				String pathUrl = md5FileName+"."+prefix;
				map.put("stat","success");
				map.put("fileMd5",md5);
				map.put("pathUrl",pathUrl);
				return responseData(map);
			}
			map.put("stat","null");
			map.put("msg","未获得数据");
			return responseData(map);
		}catch (Exception e){
			logger.error("上传视频失败：" + e);
			map.put("stat","err");
			map.put("msg","上传失败,请稍后再试！");
			return responseData(map);
		}



	}

	/**
	 * 核心平台同步数据接口
	 * @param jsonObject
	 * @return
	 */
	@RequestMapping(value = "/sysPlanData", method = RequestMethod.POST)
	public @ResponseBody String sysPlanData(@RequestBody JSONObject jsonObject){
		JSONObject result = new JSONObject();
		//校验签名
		if(!RequestSignUtil.checkSignByJSON(jsonObject)){
			result.put("code","90000");
			return result.toJSONString();
		}

		Integer pageIndex = jsonObject.getInteger("pageIndex");
		Integer pageSize = jsonObject.getInteger("pageSize");
		String lastUpdateDateStr = jsonObject.getString("lastUpdateDate");
		Date lastUpdateDate;
		if(StringUtils.isNotBlank(lastUpdateDateStr)){
			try {
				lastUpdateDate = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse(lastUpdateDateStr);
			} catch (ParseException e) {
				result.put("code","90005");
				return result.toJSONString();
			}
		}else{
			lastUpdateDate = null;
		}
		if(null == pageIndex || null == pageSize || pageIndex < 1){
			result.put("code","90006");
			return result.toJSONString();
		}
		try {
			List<SysPlanDataVo> resultList = playPlanService.getSysPlanDateVos(lastUpdateDate, pageIndex, pageSize);
			result.put("code","10000");
			result.put("pageIndex",pageIndex);
			result.put("pageSize",pageSize);
			result.put("result",resultList);
			return result.toJSONString();
		}catch (Exception e){
			logger.error("查询同步播放计划异常：" + e.getMessage());
			result.put("code","99999");
			return result.toJSONString();
		}
	}


}
